package onTheFly;

import java.util.ArrayList;
import java.util.Random;

public class HelperClass {
	int k ;
	int n ;
	public HelperClass(int k, int n) {
		super();
		this.k = k;
		this.n = n;
	}
	public int[] serverAvailability() {
		int[] servers = new int[n];
		Random random = new Random();
		for (int i = 0; i < n; i++) {
			if (random.nextDouble() < 0.8) {
				servers[i] = 1;
			} else {
				servers[i] = 0;
			}
//			System.out.print(" " + servers[i]);
		}

		return servers;

	}
	public int[][] createGeneratorMatrix() {
		Random random = new Random();
		 int[][] matrix = new int[k][n];
		for (int outerIndex = 0; outerIndex < matrix.length; outerIndex++) {
			for (int innerIndex = 0; innerIndex < matrix[outerIndex].length; innerIndex++) {
				if (random.nextDouble() < 0.5) {
					matrix[outerIndex][innerIndex] = 1;
				} else {
					matrix[outerIndex][innerIndex] = 0;
				}
			}
		}
		return matrix;
	}
	public int[][] matrixTranspose(int[][] generator) {
		int[][] transpose;
		int rows = k;
		int cols = n;
		transpose = new int[cols][rows];

		for (int h = 0; h < rows; h++) {
			for (int i = 0; i < cols; i++) {
				transpose[i][h] = generator[h][i];
			}
		}

		return transpose;
	}
	
	void printMatrix(int[][] G, int n, int k) {
		System.out.println(" Matrix :");
		for (int i = 0; i < n; i++) {
			for (int j = 0; j < k; j++) {
				System.out.print(" " + G[i][j]);
			}
			System.out.println();
		}
	}
	
	  public int[][] identity(int k) {
	        int[][] I = new int[k][k];
	        for (int i = 0; i < k; i++)
	            I[i][i] = 1;
	        return I;
	    }
	
	public int gaussianElimination(int[][] G, int[] sourceIndex) {
		// ArrayList<BitSet> ec = encodedFragments;
		// System.out.println(" original matrix");
		// printMatrix(G, k, N_new);
		// this.encodedFragments= encodedFragments;
        int result =0;
		int[][] newGenerator = new int[k][k];
		int l = 0;
		for (int i : sourceIndex) {
//			System.out.println(" GE"+i);
			for (int j = 0; j < k; j++) {
				newGenerator[l][j] = G[i][j];
			}
			l++;
		}
//		printMatrix(newGenerator, k, k);

		int n = k;
		int N = k;
		// ArrayList<String> decodedString = new ArrayList<String>();
		for (int p = 0; p < n; p++) {
			int max = p;
			for (int i = p + 1; i < N; i++) {
				if (Math.abs(newGenerator[i][p]) > Math
						.abs(newGenerator[max][p])) {
					max = i;
				}
			}
			int[] temp = newGenerator[p];
			newGenerator[p] = newGenerator[max];
			newGenerator[max] = temp;

			// System.out.println(" diagonal matrix");
			// printMatrix(G, k, N_new);

			if (Math.abs(newGenerator[p][p]) != 1) {
				throw new RuntimeException(
						"Matrix is singular or nearly singular");
			}

			for (int i = p + 1; i < N; i++) {
				int alpha = Math.abs(-(newGenerator[i][p] / newGenerator[p][p]));
			
				for (int j = p; j < n; j++) {
					newGenerator[i][j] = newGenerator[i][j]
							^ (alpha & newGenerator[p][j]);
				}
			}
//			System.out.println(" lower triangle is decode n the fly");
//			printMatrix(newGenerator, k, k);
			for (int i = 0; i <= p - 1; i++) {
				int alpha =Math.abs( -(newGenerator[i][p] / newGenerator[p][p]));
				
				for (int j = p; j < n; j++) {
					newGenerator[i][j] = newGenerator[i][j]
							^ (alpha & newGenerator[p][j]);
				}
			}
			// System.out.println(" upper triangle");
			// printMatrix(newGenerator, k, N_new);
		}
		result++;
//		printMatrix(newGenerator, k, k);
		return result;
	}
	

}
